package org.rjxh.examfront.service.impl;

import org.rjxh.examfront.mapper.ExamRoleMapper;
import org.rjxh.examfront.pojo.ExamUser;
import org.rjxh.examfront.pojo.LoginUser;
import org.rjxh.examfront.pojo.R;
import org.rjxh.examfront.service.ExamUserLoginService;
import org.rjxh.examfront.web.tools.JwtUtils;
import org.rjxh.examfront.web.tools.RedisCache;
import org.springframework.security.authentication.AuthenticationManager;
import org.springframework.security.authentication.UsernamePasswordAuthenticationToken;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.stereotype.Service;

import javax.annotation.Resource;
import java.util.HashMap;
import java.util.List;
import java.util.Objects;
import java.util.concurrent.TimeUnit;

@Service
public class ExamUserLoginServiceImpl implements ExamUserLoginService {
    @Resource
    private AuthenticationManager authenticationManager;

    @Resource
    private RedisCache redisCache;

    @Resource
    private JwtUtils jwtUtils;



    @Override
    public R login(ExamUser examUser) {
        UsernamePasswordAuthenticationToken usernamePasswordAuthenticationToken = new UsernamePasswordAuthenticationToken(examUser.getUserName(),examUser.getPassword());
        Authentication result = authenticationManager.authenticate(usernamePasswordAuthenticationToken);
        LoginUser realLoginUser = (LoginUser) result.getPrincipal();
        if (Objects.isNull(realLoginUser)) {
            //在此处直接抛出异常 由安全链的下一个处理
            throw new RuntimeException("用户名或密码错误");
        }

        //通过后生成jwt并返回

        //核验通过后的authenticate中的属性principal存放着返回的是增强的User对象
        //也就是LoginUser，前期在UserDetailsService中返回的，数据来源于数据库

        //id生成jwt
        String userId = realLoginUser.getUser().getUserId().toString();
        String jwt = jwtUtils.createJWT(userId);

        //通过后获得User对象，存入redis
        redisCache.setCacheObject("login:"+userId,realLoginUser,60, TimeUnit.MINUTES);

        HashMap<String, String> resultMap = new HashMap<>();
        resultMap.put("token",jwt);
        //验证结束 登录成功
        return new R(200,"登录成功",resultMap);
    }

    @Override
    public R logout(ExamUser user) {

        //能访问到此处 代表了经过了org.ba7lgj.filter.JwtAuthenticationTokenFilter 用户已经是登录状态
        //所以一定会有loginUser对象
        Authentication authentication = SecurityContextHolder.getContext().getAuthentication();
        LoginUser loginUser = (LoginUser) authentication.getPrincipal();
        String userId = loginUser.getUser().getUserId().toString();

        redisCache.deleteObject("login:"+userId);
        return new R(200,"成功退出");
    }
}
